﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Drawing.Text;
using System.Windows.Forms;

namespace Ma_di_tuan
{
    public class Board
    {
        #region Variables
        public static  int indexnextback=0;
        private Size m_dimension = new Size(8, 8);          // Default Chess Board Dimensions
        private Size m_parentSize = new Size(1000, 600);     // 800x600 
        private float m_ratioPercentage = 0.8f;             // Percentage amount to take from Parent.Size/Dimension.Size

        private Brush m_defaultDark = new SolidBrush(Color.FromArgb(205, 133, 63));
        private Brush m_defaultLight = new SolidBrush(Color.FromArgb(222, 184, 135));
        private Brush m_defaultHighlight = new SolidBrush(Color.FromArgb(150, 240, 255, 255));

        private List<Rectangle> List_m_highlighted1;
        #endregion

        #region Constructor
        public static int Ystart = 0;
        public static int Xstart = 0;
        public Board()
        {
            DefaultPen = new Pen(Color.Black);
            SmoothingMode = SmoothingMode.AntiAlias;
            TextRenderingHint = TextRenderingHint.AntiAlias;
            ParentSize = new Size(1000, 600);
            XOffset = 25;
            YOffset = 10;
            ListPieces1 = new List<Piece>(1);
            List_m_highlighted1 = new List<Rectangle>(1);
            CaculateSquareSize();
        }
        #endregion

        #region Methods
        protected void CaculateSquareSize()
        {
            //SquareSize = (int)Math.Min(ParentSize.Height / Dimensions.Height * m_ratioPercentage,
            //                           ParentSize.Width / Dimensions.Width * m_ratioPercentage);
            SquareSize = 30;
        }

        public virtual void Render(Graphics graphics)
        {
            XOffset = 24;
            graphics.Clear(Color.White);
            graphics.SmoothingMode = this.SmoothingMode;
            graphics.TextRenderingHint = this.TextRenderingHint;

            bool darkFlag = true; // Hack - maybe there is a better way, but in a chessboard it will always work.
            for (int h = 0; h < Dimensions.Height; h++)
            {
                for (int w = 0; w < Dimensions.Width; w++)
                {
                    // Create Rectangle
                    Rectangle rect = new Rectangle(w * SquareSize + XOffset+Xstart,
                                                   h * SquareSize + YOffset+Ystart,
                                                   SquareSize,
                                                   SquareSize);
                    // Fill Rectangle
                    graphics.FillRectangle(darkFlag ? m_defaultDark : m_defaultLight, rect);

                    // Draw Border
                    graphics.DrawRectangle(DefaultPen, rect);

                    // Reverse
                    darkFlag = !darkFlag;
                }

                // New Row Reverse
                darkFlag = !darkFlag;
            }

            // Other Logic
            foreach (Rectangle rect in List_m_highlighted1)
                graphics.FillRectangle(m_defaultHighlight, rect);

            // ListPieces1
            RenderPieces(graphics);
        }
           
        private void RenderPieces(Graphics graphics)
        {
            
            foreach (Piece piece in ListPieces1)// that ra chi co 1 con knight thoi
            {
                int h = piece.Loc.Row * SquareSize + YOffset+Ystart;
                int w = piece.Loc.Rank * SquareSize + XOffset+Xstart;
                Rectangle rect = new Rectangle(w,
                                               h,
                                               SquareSize,
                                               SquareSize);
                Point point = new Point(rect.X + SquareSize /4,
                                        rect.Y + SquareSize /4);

              //  piece.Render(graphics, point,"");

                // Test Code
                //foreach (Location loc in piece.GetAvailableMoves())
                //{
                //    h = loc.Row * SquareSize + YOffset;
                //    w = loc.Rank * SquareSize + XOffset;
                //    rect = new Rectangle(w,
                //                         h,
                //                         SquareSize,
                //                         SquareSize);
                //    graphics.FillRectangle(m_defaultHighlight, rect);
                //}

                // Test Code
                Point prevPoint = new Point(0, 0);
                Pen pen = new Pen(new SolidBrush(Color.Black));
                int count = 0;
                if (indexnextback <0)
                {
                    return;
                }
                if (piece.ListMoves == null||piece.ListMoves.Count==1)
                {
                    return;
                }
                foreach (Location loc in piece.ListMoves.GetRange(0,indexnextback))
                {
                    count++;
                    h = loc.Row * SquareSize + YOffset+Ystart;
                    w = loc.Rank * SquareSize +XOffset+Xstart;
                    rect = new Rectangle(w,
                                         h,
                                         SquareSize,
                                         SquareSize);
                    
                    graphics.FillRectangle(m_defaultHighlight, rect);
                    graphics.DrawRectangle(pen, new Rectangle(rect.X + SquareSize / 2 - 2,
                                                              rect.Y + SquareSize / 2 - 2,
                                                              4,
                                                              4));
                    graphics.FillRectangle(new SolidBrush(Color.Black), new Rectangle(rect.X + SquareSize / 2 - 2,
                                                              rect.Y + SquareSize / 2 - 2,
                                                              4,
                                                              4));                   
                    point = new Point(rect.X + SquareSize / 2,
                                     rect.Y + SquareSize / 2);                                      
                    if (count == indexnextback)
                    {
                        graphics.DrawString(count.ToString(), new Font("Arial", 9f), new SolidBrush(Color.Red), point.X + 1, point.Y);
                    }
                    else
                    {
                        graphics.DrawString(count.ToString(), new Font("Arial", 9f), new SolidBrush(Color.Blue), point.X + 1, point.Y);
                    }
                        
                    if (count > 1)
                    {
                    graphics.DrawLine(pen, prevPoint, point);
                    }
                       
                    
                    prevPoint = point;
                }
            }
          
        }

        public int GetRow(Point location)
        {
            return (location.Y - YOffset) / SquareSize;
        }

        public int GetRank(Point location)
        {
            return (location.X - XOffset) / SquareSize;
        }

        public T GetPiece<T>(Point location)
        {
            object piece = null;

            piece = (from p in ListPieces1
                     where p.Loc.Rank == GetRank(location) && p.Loc.Row == GetRow(location)
                     select p).FirstOrDefault();

            return (T)piece;
        }

        public T GetPiece<T>(int row, int rank)
        {
            object piece = null;

            piece = (from p in ListPieces1
                     where p.Loc.Rank == rank && p.Loc.Row == row
                     select p).FirstOrDefault();

            return (T)piece;
        }

        public string GetSquareName(Point location)
        {
            return string.Format("Row {0}, Rank {1}", GetRow(location), GetRank(location));
        }

        public void AddHighlight(Point location)
        {
            int h = GetRow(location) * SquareSize + YOffset;
            int w = GetRank(location) * SquareSize + XOffset;

            List_m_highlighted1.Clear();
            List_m_highlighted1.Add(new Rectangle(w,
                                            h,
                                            SquareSize,
                                            SquareSize));
        }
        #endregion

        #region Properties
        public List<Piece> ListPieces1 { get; set; }

        public float RatioPercentage
        {
            get { return m_ratioPercentage; }
            set
            {
                m_ratioPercentage = value;
                CaculateSquareSize();
            }
        }

        public SmoothingMode SmoothingMode { get; set; }

        public TextRenderingHint TextRenderingHint { get; set; }

        public Size Dimensions
        {
            get { return m_dimension; }
            set
            {
                m_dimension = value;
                CaculateSquareSize();
            }
        }

        public Size ParentSize
        {
            get { return m_parentSize; }
            set
            {
                m_parentSize = value;
                CaculateSquareSize();
            }
        }

        public int XOffset { get; set; }
        public int YOffset { get; set; }
        public int SquareSize { get; set; }
        public Pen DefaultPen { get; set; }
        #endregion
    }
}
